package cn.texous.easytalk.manager.config;

import cn.texous.easytalk.commonutil.constant.Result;
import cn.texous.easytalk.commonutil.constant.ResultCode;
import cn.texous.easytalk.commonutil.exception.BusinessException;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.NoHandlerFoundException;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

/**
 * controller 异常统一处理配置
 *
 * @author Showa.L
 * @since 2019/09/02 10:43
 */
@Slf4j
@ControllerAdvice
public class ExceptionHandlerConfig {

    @Autowired
    private ObjectMapper objectMapper;

    /**
     * 捕获可预见异常
     *
     * @param response 结果返回
     * @param ex       异常
     * @return
     */
    @ExceptionHandler(BusinessException.class)
    public ModelAndView handlerBusinessException(HttpServletResponse response,
                                                 BusinessException ex) {
        log.error(String.format("businesss exception【code=%s, desc=%s】",
                ex.getCode(), ex.getMessage()), ex);
        Result result = Result.out(ex.getCode(), ex.getMessage(), null);
        return responseResult(response, result);
    }

    /**
     * 捕获不可预见异常
     *
     * @param request  请求
     * @param response 结果
     * @param e        异常
     * @return
     */
    @ExceptionHandler(RuntimeException.class)
    public ModelAndView handlerException(HttpServletRequest request,
                                         HttpServletResponse response,
                                         Exception e) {
        Result result;
        String errorMsg;
        if (e instanceof NoHandlerFoundException) {
            errorMsg = "api [" + request.getRequestURI() + "] nothing";
            result = Result.out(ResultCode.NOT_FOUND);
        } else {
            errorMsg = "api [" + request.getRequestURI() + "] error，plase later try again!";
            result = Result.out(ResultCode.INTERNAL_SERVER_ERROR);
        }
        // String loggerMessage = e.getMessage();
        log.error(String.format("handler exception: 【%s】", errorMsg), e);
        responseResult(response, result);
        return new ModelAndView();
    }

    private ModelAndView responseResult(HttpServletResponse response, Result result) {
        response.setCharacterEncoding("UTF-8");
        response.setHeader("Content-type", "application/json;charset=UTF-8");
        response.setStatus(200);
        try {
            response.getWriter().write(objectMapper.writeValueAsString(result));
        } catch (IOException ex) {
            log.error(ex.getMessage());
        }
        return new ModelAndView();
    }

}
